﻿using Microsoft.VisualStudio.TestTools.UnitTesting;
using Negocio = PSE.Tools.CadastroMensagens.Negocio;
using Entidades = PSE.Tools.CadastroMensagens.Entidades;
using PSE.Tools.Util.Entidades;
using System;
using System.Linq;
using System.Text;

namespace CadastroMensagensTest
{
    [TestClass()]
    public class IdiomasTest
    {
        #region [ Métodos Auxiliares ]
        private string RetornaNovaSigla()
        {
            var sigla = StringUtil.RetornaTextoAleatorio(5);
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            var retorno = true;
            while (retorno)
            {
                var idioma = negocio.ObterPorSigla(sigla);
                retorno = (idioma != null);
            }
            return sigla;
        }
        #endregion [ Métodos Auxiliares ]

        #region [ Inserir ]
        [TestMethod]
        public void InsereIdiomaComEntidadeNula()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                negocio.Inserir(null);
            }
            catch (System.ArgumentNullException)
            {
                ok = true;
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void InsereIdiomaComSiglaVazia()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                Entidades.Idioma idioma = new Entidades.Idioma();
                idioma.Sigla = "";
                idioma.Descricao = "teste";
                negocio.Inserir(idioma);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Sigla", System.StringComparison.CurrentCultureIgnoreCase);
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void InsereIdiomaComSiglaComMaisDe6Caracteres()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                Entidades.Idioma idioma = new Entidades.Idioma();
                idioma.Sigla = "xptoxpto";
                idioma.Descricao = "teste";
                negocio.Inserir(idioma);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Sigla", System.StringComparison.CurrentCultureIgnoreCase);
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void InsereIdiomaComDescricaoVazia()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                Entidades.Idioma idioma = new Entidades.Idioma();
                idioma.Sigla = "xpto";
                idioma.Descricao = "";
                negocio.Inserir(idioma);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Descricao", System.StringComparison.CurrentCultureIgnoreCase);
            }
            Assert.IsTrue(ok);
        }
        
        [TestMethod]
        public void InsereIdiomaComSiglaJaCadastrada()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            var entidadeJaExistente = negocio.Selecionar()[0];
            Entidades.Idioma entidadeNova = new Entidades.Idioma {  Sigla = entidadeJaExistente.Sigla, Descricao = "Teste" };
            try
            {
                negocio.Inserir(entidadeNova);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Sigla");
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void InsereIdiomaComDescricaoJaCadastrada()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            var entidadeJaExistente = negocio.Selecionar()[0];
            Entidades.Idioma entidadeNova = new Entidades.Idioma { Sigla = "Xpto", Descricao = entidadeJaExistente.Descricao };
            try
            {
                negocio.Inserir(entidadeNova);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Descricao");
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void InsereIdiomaComSucesso()
        {
            bool ok = true;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            string sigla = RetornaNovaSigla();
            string descricao = "TesteInserir" + sigla;
            Entidades.Idioma entidadeNova = new Entidades.Idioma { Sigla = sigla, Descricao = descricao };
            try
            {
                negocio.Inserir(entidadeNova);
            }
            catch (Exception)
            {
                ok = false;
            }
            Assert.IsTrue(ok);        
        }
        #endregion [ Inserir ]

        #region [ Atualizar ]
        [TestMethod]
        public void AtualizaIdiomaComEntidadeNula()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                negocio.Atualizar(null);
            }
            catch (System.ArgumentNullException)
            {
                ok = true;
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void AtualizaIdiomaComSiglaVazia()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                Entidades.Idioma idioma = negocio.Selecionar()[0];
                idioma.Sigla = "";
                idioma.Descricao = "teste";
                negocio.Atualizar(idioma);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Sigla", System.StringComparison.CurrentCultureIgnoreCase);
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void AtualizaIdiomaComDescricaoVazia()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                Entidades.Idioma idioma = negocio.Selecionar()[0];
                idioma.Sigla = "teste";
                idioma.Descricao = "";
                negocio.Atualizar(idioma);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Descricao", System.StringComparison.CurrentCultureIgnoreCase);
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void AtualizaIdiomaComSiglaComMaisDe6Caracteres()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                Entidades.Idioma idioma = negocio.Selecionar()[0];
                idioma.Sigla = "xptoxpto";
                idioma.Descricao = "teste";
                negocio.Atualizar(idioma);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Sigla", System.StringComparison.CurrentCultureIgnoreCase);
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void AtualizaIdiomaComDescricaoJaCadastrada()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            Entidades.Idioma idioma1 = negocio.Selecionar()[0];
            Entidades.Idioma idioma2 = negocio.Selecionar()[1];
            idioma2.Descricao = idioma1.Descricao;
            try
            {
                negocio.Atualizar(idioma2);
            }
            catch (ValidacaoEntidadeException ex)
            {
                ok = ex.Validacoes.First().NomePropriedade.Equals("Descricao");
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void AtualizaIdiomaComSucesso()
        {
            bool ok = true;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            Entidades.Idioma idioma = negocio.Selecionar()[0];
            try
            {
                negocio.Atualizar(idioma);
            }
            catch (Exception)
            {
                ok = false;
            }
            Assert.IsTrue(ok);
        }
        #endregion [ Atualizar ]

        #region [ Excluir ]
        [TestMethod]
        public void ExcluirIdiomaNulo()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                negocio.Excluir(null);
            }
            catch (ArgumentNullException)
            {
                ok = true;
            }
            catch (Exception)
            {
                ok = false;
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void ExcluirIdiomaComSucesso()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            string sigla = RetornaNovaSigla();
            string descricao = "TesteExcluir" + sigla;
            Entidades.Idioma entidadeNova = new Entidades.Idioma { Sigla = sigla, Descricao = descricao };

            try
            {
                negocio.Inserir(entidadeNova);
                var entidade = negocio.ObterPorSigla(sigla);
                negocio.Excluir(entidade);
                entidade = negocio.ObterPorSigla(sigla);
                ok = (entidade == null);
            }
            catch (Exception)
            {
                ok = false;
            }
            Assert.IsTrue(ok);
        }
        #endregion [ Excluir ]

        #region [ Obter ]
        [TestMethod]
        public void ObterIdiomaComSiglaVazia()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                var idioma = negocio.ObterPorSigla("");
            }
            catch (ArgumentNullException)
            {
                ok = true;
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void ObterIdiomaComSucesso()
        {
            bool ok = true;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            string sigla = RetornaNovaSigla();
            string descricao = "TesteInserir" + sigla;
            Entidades.Idioma entidadeNova = new Entidades.Idioma { Sigla = sigla, Descricao = descricao };
            try
            {
                negocio.Inserir(entidadeNova);
                var entidade = negocio.ObterPorSigla(sigla);
                ok = (entidade != null);
            }
            catch (Exception)
            {
                ok = false;
            }
            Assert.IsTrue(ok);
        }
        #endregion [ Obter ]

        #region [ Selecionar ]
        [TestMethod]
        public void SelecionarIdiomasComSucesso()
        {
            bool ok = true;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            string sigla = RetornaNovaSigla();
            string descricao = "TesteInserir" + sigla;
            Entidades.Idioma entidadeNova = new Entidades.Idioma { Sigla = sigla, Descricao = descricao };
            try
            {
                negocio.Inserir(entidadeNova);
                var entidade = negocio.ObterPorSigla(sigla);
                ok = negocio.Selecionar().Count > 0;
            }
            catch (Exception)
            {
                ok = false;
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void SelecionarIdiomasComFiltroInvalido()
        {
            bool ok = false;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            try
            {
                var entidades = negocio.Selecionar(null);
            }
            catch (ArgumentNullException)
            {
                ok = true;
            }
            Assert.IsTrue(ok);
        }

        [TestMethod]
        public void SelecionarIdiomasComFiltroPelaSigla()
        {
            bool ok = true;
            Negocio.Idiomas negocio = new Negocio.Idiomas();
            string sigla = RetornaNovaSigla();
            string descricao = "TesteInserir" + sigla;
            Entidades.Idioma entidadeNova = new Entidades.Idioma { Sigla = sigla, Descricao = descricao };
            try
            {
                negocio.Inserir(entidadeNova);
                var entidades = negocio.Selecionar(i => i.Sigla.Equals(sigla));
                ok = entidades.Count == 1;
            }
            catch (Exception)
            {
                ok = false;
            }
            Assert.IsTrue(ok);
        }
        #endregion [ Selecionar ]
    }
}
